//*********************************************************
//
//    Copyright (c) Microsoft. All rights reserved.
//    This code is licensed under the Apache License, Version 2.0.
//    THIS CODE IS PROVIDED *AS IS* WITHOUT WARRANTY OF
//    ANY KIND, EITHER EXPRESS OR IMPLIED, INCLUDING ANY
//    IMPLIED WARRANTIES OF FITNESS FOR A PARTICULAR
//    PURPOSE, MERCHANTABILITY, OR NON-INFRINGEMENT.
//
//*********************************************************

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;
using System.Runtime.Serialization;
using System.Runtime.Serialization.Formatters.Soap;
using Microsoft.Research.DataLayer;

namespace Microsoft.Research.DataLayer
{
    /// <summary>
    /// Class for packing enum types while sending queries
    /// over the n/w.
    /// </summary>
    [Serializable]
    public class XferEnumReference : BaseField
    {
        /// <summary>
        /// Constructor.
        /// </summary>
        public XferEnumReference() : base("TransferEnumRef")
        {
        }

        /// <summary>
        /// Type of the enum object
        /// </summary>
        public string objectType;

        /// <summary>
        /// Static method for creating the search clause
        /// </summary>
        public string staticMethodName;

        /// <summary>
        /// Enum condition for the query.
        /// </summary>
        public string enumConditionType;

        /// <summary>
        /// Value for the enum condition.
        /// </summary>
        public string enumConditionValue;

        /// <summary>
        /// Type of the enum value
        /// </summary>
        public string enumValueType;
        
        /// <summary>
        /// Enum value
        /// </summary>
        public string enumValueValue;
    }

    /// <summary>
    /// Class for packing object types while sending queries
    /// over the n/w.
    /// </summary>
    [Serializable]
    public class XferObjectField : BaseField
    {
        /// <summary>
        /// Constructor
        /// </summary>
        public XferObjectField()
            : base("XferObjectField")
        {
        }

        /// <summary>
        /// Type of the object used in the search query
        /// </summary>
        public string objectType;

        /// <summary>
        /// Static method name to create the object field
        /// </summary>
        public string staticMethodName;

        /// <summary>
        /// Type of the condition clause
        /// </summary>
        public string enumConditionType;

        /// <summary>
        /// Condtion value
        /// </summary>
        public string enumConditionValue;

        /// <summary>
        /// Object instance used in the search clause
        /// </summary>
        public object searchObject;
    }

    /// <summary>
    /// Class for packing relation objects
    /// </summary>
    [Serializable]
    public class XferObjectReference2
    {
        /// <summary>
        /// Id of the relation object.
        /// </summary>
        public Guid Id;

        /// <summary>
        /// Contents of the relation object as raw bytes.
        /// </summary>
        private byte[] storage;

        /// <summary>
        /// Method for converting relation object to a proxy 
        /// for sending over the wire.
        /// </summary>
        /// <param name="id"></param>
        /// <param name="type"></param>
        public void Pack(Guid id, Connection.Storage type)
        {
            this.Id = id;
            MemoryStream ms = new MemoryStream();
            IFormatter fmt = new SoapFormatter();
            fmt.Serialize(ms, type);
            storage = ms.ToArray();
        }

        /// <summary>
        /// Method for unpacking the relation object
        /// </summary>
        /// <returns></returns>
        public Connection.Storage UnPackObjType()
        {
            Connection.Storage ret;
            MemoryStream ms = new MemoryStream(this.storage);
            IFormatter fmt = new SoapFormatter();
            ret = (Connection.Storage)fmt.Deserialize(ms);
            return ret;
        }
    }
}
